package com.threeti.mecool.core.infrastructure.persistence.project;

import com.threeti.mecool.core.domain.model.project.Project;
import com.threeti.mecool.core.domain.model.project.ProjectStatus;
import com.threeti.mecool.core.domain.model.project.ProjectStore;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.Pageable;
import org.springframework.data.jpa.repository.JpaRepository;
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
import org.springframework.data.jpa.repository.Modifying;
import org.springframework.data.jpa.repository.Query;
import org.springframework.transaction.annotation.Transactional;

import java.util.Collection;
import java.util.List;
import java.util.Map;

/**
 * TODO jay:this public repo may damage the aggregationroot(project) constraints
 */
public interface ProjectStoreRepository extends JpaRepository<ProjectStore, Long>, JpaSpecificationExecutor<ProjectStore> {

    /**
     * 分页取得特定项目的项目门店(终端)集合
     */
    Page<ProjectStore> findByProjectId(Long projId, Pageable pageable);

    /**
     * 直接取得特定项目的项目门店(终端)集合,集合可能很大，所以请慎用本方法
     */
    @Deprecated
    List<ProjectStore> findByProjectId(Long projId);

    /**
     * 取得指定项目集所包含的项目门店(终端)集合<p>
     * <p/>
     * 1.返回集合中，虽然项目门店实体本身不会产生重复，但项目门店的显示名称可能会产生重复
     */
    List<ProjectStore> findByProjectIn(Collection<Project> projects);

    /**
     * 分页取得指定项目门店集合以外的项目门店(终端)集合
     */
    Page<ProjectStore> findByProjectIdAndIdNotIn(Long projectId, Collection<Long> projStoreIds, Pageable pageable);

    /**
     * 删除特定项目的所有项目门店(终端)集合<p>
     */
    @Modifying
    @Transactional
    @Query("delete from ProjectStore ps where ps.project.id = ?1")
    void deleteByProjectId(Long projectId);

    /**
     * 根据项目状态，取得特定城市下的(计划)门店<p>
     * <p/>
     * 1.返回集合中门店名称可能产生重复，因为不同项目可能门店名称是一样的<br/>
     * 2.本方法一般用于报表或者搜索，返回的是某城市下所有的计划门店集合，并且输入项目状态应该是ACTIVE
     */
    List<ProjectStore> findByProjectStatusAndChannel_Channel_AdCode(ProjectStatus status, String adCode);

    /**
     * 根据项目状态，取得特定城市下的(计划)门店<p>
     * <p/>
     * 1.返回集合中门店名称可能产生重复，因为不同项目可能门店名称是一样的<br/>
     * 2.本方法一般用于报表或者搜索，返回的是某城市下所有的计划门店集合，并且输入项目状态应该是ACTIVE
     */
    List<ProjectStore> findByProjectStatusAndChannel_Channel_CityAdCode(ProjectStatus status, String cityAdCode);

    /**
     * 根据项目状态，取得特定省市下的(计划)门店<p>
     * <p/>
     * 1.返回集合中门店名称可能产生重复，因为不同项目可能门店名称是一样的<br/>
     * 2.本方法一般用于报表或者搜索，返回的是某省市下所有的计划门店集合，并且输入项目状态应该是ACTIVE
     */
    List<ProjectStore> findByProjectStatusAndChannel_Channel_ProvinceAdCode(ProjectStatus status, String provinceAdCode);

    ProjectStore findByProject_CodeAndChannel_Channel_Code(String projectCode, String channelCode);

    
    @Query(nativeQuery=true,value="select t1.id, "+
						    		"     t1.channel, "+
						    		"     t1.channel_code, "+
						    		"     t1.project, "+
						    		"     t1.required_sales_number, "+
														       
									"     t3.channel_address, "+
									"  	  t3.channel_name, "+
									" 	  t3.channel_ad_name, "+
									"  	  t3.channel_city_ad_name, "+
									"     t2.name as project_name "+
									
									"     from dm_project_store t1, dm_project t2, dm_channel_sync t3 "+
									" 	  where t1.project = t2.id "+
									"  	  and t1.channel = t3.id "+
									"  	  and t2.status = ?1 " +
									"  	  and t3.channel_city_ad_code = ?2 ")
	List<Map> findByProjectStatusAndChannelCityAdCode(int active,String standardAdminDivAreaCode);
}
